package com.boot.controller;

import com.boot.dto.HistoricProcessInstanceDto;
import com.boot.dto.ProcessDefinitionDto;
import com.boot.dto.ProcessInstanceDto;
import com.boot.dto.TaskDto;
import org.camunda.bpm.engine.HistoryService;
import org.camunda.bpm.engine.RepositoryService;
import org.camunda.bpm.engine.RuntimeService;
import org.camunda.bpm.engine.TaskService;
import org.camunda.bpm.engine.repository.Deployment;
import org.camunda.bpm.engine.runtime.ProcessInstance;
import org.springframework.web.bind.annotation.*;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@RestController
@RequestMapping("/api/workflow")
@CrossOrigin(origins = "*", maxAge = 3600)
public class WorkflowController {

    private final RuntimeService runtimeService;
    private final TaskService taskService;
    private final RepositoryService repositoryService;
    private final HistoryService historyService;

    public WorkflowController(RuntimeService runtimeService, TaskService taskService, RepositoryService repositoryService, HistoryService historyService) {
        this.runtimeService = runtimeService;
        this.taskService = taskService;
        this.repositoryService = repositoryService;
        this.historyService = historyService;
    }

    // ==================== 流程定义相关 ====================

    /**
     * 获取所有流程定义列表
     */
    @GetMapping("/definitions")
    public List<ProcessDefinitionDto> getProcessDefinitions() {
        return repositoryService.createProcessDefinitionQuery()
                .latestVersion()
                .list()
                .stream()
                .map(ProcessDefinitionDto::from)
                .collect(Collectors.toList());
    }

    /**
     * 部署流程（可手动调用，也可配置自动部署）
     */
    @PostMapping("/deploy")
    public String deployProcess() {
        Deployment deployment = repositoryService.createDeployment()
                .addClasspathResource("bpmn/simple-process.bpmn")
                .name("简单流程部署")
                .deploy();
        return "部署成功，ID=" + deployment.getId();
    }

    // ==================== 流程实例相关 ====================

    /**
     * 启动流程实例
     */
    @PostMapping("/start/{processKey}")
    public String startProcess(@PathVariable String processKey, @RequestBody(required = false) Map<String, Object> variables) {
        if (variables == null) variables = new HashMap<>();
        ProcessInstance instance = runtimeService.startProcessInstanceByKey(processKey, variables);
        return "流程启动成功，实例ID: " + instance.getId() + ", 流程定义ID: " + instance.getProcessDefinitionId();
    }

    /**
     * 获取所有运行中的流程实例
     */
    @GetMapping("/instances/running")
    public List<ProcessInstanceDto> getRunningInstances() {
        return runtimeService.createProcessInstanceQuery().active().list()
                .stream()
                .map(ProcessInstanceDto::from)
                .collect(Collectors.toList());
    }

    /**
     * 获取历史流程实例（包括结束的）
     */
    @GetMapping("/instances/history")
    public List<HistoricProcessInstanceDto> getHistoricInstances() {
        return historyService.createHistoricProcessInstanceQuery()
                .orderByProcessInstanceStartTime().desc()
                .list()
                .stream()
                .map(HistoricProcessInstanceDto::from)
                .collect(Collectors.toList());
    }

    // ==================== 用户任务相关 ====================

    /**
     * 获取指定用户的待办任务列表
     */
    @GetMapping("/tasks")
    public List<TaskDto> getUserTasks(@RequestParam String assignee) {
        return taskService.createTaskQuery()
                .taskAssignee(assignee)
                .active()
                .list()
                .stream()
                .map(TaskDto::from)
                .collect(Collectors.toList());
    }

    /**
     * 完成用户任务（可传递变量）
     */
    @PostMapping("/task/{taskId}/complete")
    public String completeTask(@PathVariable String taskId, @RequestBody(required = false) Map<String, Object> variables) {
        if (variables == null) variables = new HashMap<>();
        try {
            taskService.complete(taskId, variables);
            return "任务完成，ID=" + taskId;
        } catch (Exception e) {
            return "任务完成失败: " + e.getMessage();
        }
    }

    /**
     * 查询所有任务（调试用）
     */
    @GetMapping("/tasks/all")
    public List<TaskDto> getAllTasks() {
        return taskService.createTaskQuery().list()
                .stream()
                .map(TaskDto::from)
                .collect(Collectors.toList());
    }
}
